package com.duoec.dw.lineage.service.analyser.order;

import com.alibaba.druid.sql.ast.SQLExpr;
import com.alibaba.druid.sql.ast.SQLOrderBy;
import com.duoec.dw.lineage.dto.TableFieldDependencyDto;
import com.duoec.dw.lineage.dto.TableLineageDto;
import com.duoec.dw.lineage.exceptions.FieldNotFoundLineageAnalyserException;
import com.duoec.dw.lineage.service.analyser.HiveOrderByAnalyser;
import com.duoec.dw.lineage.core.utils.AnalyserUtils;
import com.duoec.dw.lineage.dto.MultiTableLineageDto;
import com.duoec.dw.lineage.service.HiveAnalyser;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.LinkedHashSet;

/**
 * @author xuwenzhen
 */
@Service
public class OrderByAnalyser implements HiveOrderByAnalyser {
    @Autowired
    protected HiveAnalyser hiveAnalyser;

    /**
     * 获取当前类处理的类型
     *
     * @return SQLOrderBy子类类型
     */
    @Override
    public Class<SQLOrderBy> getType() {
        return SQLOrderBy.class;
    }

    /**
     * 解析 order by
     *
     * @param orderBy           order by语句
     * @param fromTableLineages from解析出来的多个血缘关系数据
     * @param tableLineage      当前语句的血缘关系数据
     */
    @Override
    public void analyse(SQLOrderBy orderBy, MultiTableLineageDto fromTableLineages, TableLineageDto tableLineage) {
        LinkedHashSet<TableFieldDependencyDto> dependencies = new LinkedHashSet<>();
        orderBy.getItems().forEach(item -> {
            SQLExpr expr = item.getExpr();
            try {
                LinkedHashSet<TableFieldDependencyDto> dependencies2 = hiveAnalyser.analyseExpr(fromTableLineages, expr);
                AnalyserUtils.mergeToDependencies(dependencies, dependencies2);
            } catch (FieldNotFoundLineageAnalyserException e) {
                //尝试从当前表中查找
                MultiTableLineageDto selfTable = new MultiTableLineageDto();
                selfTable.add(tableLineage);

                LinkedHashSet<TableFieldDependencyDto> dependencies2 = hiveAnalyser.analyseExpr(selfTable, expr);
                AnalyserUtils.mergeToDependencies(dependencies, dependencies2);
            }
        });
        tableLineage.getDependencies().addAll(dependencies);
    }

    public void setHiveAnalyser(HiveAnalyser hiveAnalyser) {
        this.hiveAnalyser = hiveAnalyser;
    }
}
